#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
第1阶段逻辑验证和页面分析脚本
验证车型轮播抓取的完整流程
"""

import json
import time
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.service import Service
from webdriver_manager.chrome import ChromeDriverManager
from selenium.common.exceptions import TimeoutException, NoSuchElementException

class Stage1Analyzer:
    """第1阶段分析器"""
    
    def __init__(self):
        self.setup_driver()
        self.analysis_data = {
            "cookies_handled": False,
            "initial_cars_found": 0,
            "carousel_navigation": {
                "next_button_clicks": 0,
                "prev_button_clicks": 0,
                "total_carousel_cycles": 0
            },
            "cars_discovered": [],
            "final_car_count": 0,
            "analysis_notes": []
        }
    
    def setup_driver(self):
        """设置Chrome WebDriver"""
        chrome_options = Options()
        chrome_options.add_argument('--disable-blink-features=AutomationControlled')
        chrome_options.add_experimental_option("excludeSwitches", ["enable-automation"])
        chrome_options.add_experimental_option('useAutomationExtension', False)
        chrome_options.add_argument('--user-agent=Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/17.1 Safari/605.1.15')
        
        service = Service(ChromeDriverManager().install())
        self.driver = webdriver.Chrome(service=service, options=chrome_options)
        self.wait = WebDriverWait(self.driver, 10)
    
    def analyze_stage1_logic(self):
        """分析第1阶段完整逻辑"""
        try:
            print("🔍 开始第1阶段逻辑验证和分析...")
            
            # 步骤1：访问页面
            url = "https://www.ford.co.uk/shop/build-your-ford/ngc2/ice2/model?catalogId=WAEGB-CGE-2022-FocusMCAGBR202450&series=ACMAA_VS-D3&paint=PN4A7&planId=c"
            print(f"\n📖 步骤1：访问目标页面")
            print(f"URL: {url}")
            
            self.driver.get(url)
            time.sleep(5)
            
            # 步骤2：处理Cookie确认
            print(f"\n🍪 步骤2：处理Cookie确认")
            cookies_handled = self.handle_cookies()
            self.analysis_data["cookies_handled"] = cookies_handled
            
            # 步骤3：分析初始页面状态
            print(f"\n🎠 步骤3：分析车型轮播初始状态")
            initial_analysis = self.analyze_initial_carousel_state()
            
            # 步骤4：执行轮播导航获取所有车型
            print(f"\n🔄 步骤4：执行轮播导航获取所有车型")
            carousel_analysis = self.perform_carousel_navigation()
            
            # 步骤5：验证最终结果
            print(f"\n✅ 步骤5：验证最终结果")
            final_verification = self.verify_final_results()
            
            # 生成分析报告
            self.generate_analysis_report()
            
            return True
            
        except Exception as e:
            print(f"❌ 分析过程出错: {e}")
            return False
        finally:
            input("按Enter键关闭浏览器...")
            self.driver.quit()
    
    def handle_cookies(self):
        """处理Cookie确认弹窗"""
        try:
            # 查找Cookie相关的弹窗和按钮
            cookie_selectors = [
                'button:contains("Accept")',
                'button:contains("同意")',
                'button:contains("允许")',
                '[class*="cookie"] button',
                '[class*="Cookie"] button',
                '[data-cy*="cookie"] button',
                'button[class*="accept"]',
                'button[class*="Accept"]'
            ]
            
            cookie_found = False
            for selector in cookie_selectors:
                try:
                    if 'contains' in selector:
                        # 使用XPath for contains
                        button_text = selector.split('contains("')[1].split('")')[0]
                        xpath_selector = f"//button[contains(text(), '{button_text}')]"
                        elements = self.driver.find_elements(By.XPATH, xpath_selector)
                    else:
                        elements = self.driver.find_elements(By.CSS_SELECTOR, selector)
                    
                    for element in elements:
                        if element.is_displayed() and element.is_enabled():
                            print(f"  ✓ 找到Cookie按钮: {element.text}")
                            self.driver.execute_script("arguments[0].click();", element)
                            time.sleep(2)
                            cookie_found = True
                            print(f"  ✅ 成功点击Cookie确认按钮")
                            break
                    
                    if cookie_found:
                        break
                        
                except Exception:
                    continue
            
            if not cookie_found:
                print(f"  ⚠️  未找到明显的Cookie确认按钮，尝试强制清理...")
                # 强制移除可能的Cookie弹窗
                cookie_containers = self.driver.find_elements(By.CSS_SELECTOR, '[class*="cookie"], [class*="Cookie"], [class*="consent"]')
                removed_count = 0
                for container in cookie_containers:
                    try:
                        if container.is_displayed():
                            self.driver.execute_script("arguments[0].style.display = 'none';", container)
                            removed_count += 1
                    except:
                        pass
                
                if removed_count > 0:
                    print(f"  ✓ 强制隐藏了 {removed_count} 个潜在Cookie元素")
                    cookie_found = True
                else:
                    print(f"  ℹ️  页面可能没有Cookie弹窗")
            
            return cookie_found
            
        except Exception as e:
            print(f"  ❌ 处理Cookie时出错: {e}")
            return False
    
    def analyze_initial_carousel_state(self):
        """分析车型轮播的初始状态"""
        try:
            # 查找车型元素
            car_selectors = [
                'div[data-cy][class*="ProductTile"]',
                '[data-cy][class*="Tile"]',
                '[class*="ProductTile"]'
            ]
            
            cars_found = []
            for selector in car_selectors:
                try:
                    elements = self.driver.find_elements(By.CSS_SELECTOR, selector)
                    if elements:
                        print(f"  ✓ 使用选择器 '{selector}' 找到 {len(elements)} 个车型元素")
                        
                        for i, element in enumerate(elements):
                            car_info = self.extract_car_basic_info(element, i+1)
                            if car_info:
                                cars_found.append(car_info)
                        
                        break
                except Exception as e:
                    print(f"  选择器 {selector} 出错: {e}")
                    continue
            
            self.analysis_data["initial_cars_found"] = len(cars_found)
            self.analysis_data["cars_discovered"] = cars_found
            
            print(f"  📊 初始状态分析:")
            print(f"    - 找到车型元素: {len(cars_found)} 个")
            for car in cars_found:
                visibility = "可见" if car["visible"] else "隐藏"
                print(f"    - {car['name']}: {visibility}, 价格: {car['price']}")
            
            # 分析轮播控制按钮
            self.analyze_carousel_controls()
            
            return cars_found
            
        except Exception as e:
            print(f"  ❌ 分析初始状态时出错: {e}")
            return []
    
    def extract_car_basic_info(self, element, index):
        """提取车型基本信息"""
        try:
            car_info = {
                "index": index,
                "name": "Unknown",
                "price": "Unknown", 
                "data_cy": "",
                "visible": element.is_displayed(),
                "in_viewport": False,
                "element": element
            }
            
            # 获取data-cy属性
            data_cy = element.get_attribute('data-cy')
            if data_cy:
                car_info["data_cy"] = data_cy
                car_info["name"] = data_cy
            
            # 获取价格信息
            price_selectors = [
                '[class*="price"]',
                '[class*="Price"]',
                '*[text()[contains(., "£")]]'
            ]
            
            for price_selector in price_selectors:
                try:
                    if 'text()' in price_selector:
                        # XPath selector
                        price_elements = element.find_elements(By.XPATH, ".//*[contains(text(), '£')]")
                    else:
                        price_elements = element.find_elements(By.CSS_SELECTOR, price_selector)
                    
                    for price_elem in price_elements:
                        price_text = price_elem.text.strip()
                        if '£' in price_text:
                            car_info["price"] = price_text
                            break
                    
                    if car_info["price"] != "Unknown":
                        break
                        
                except Exception:
                    continue
            
            # 检查是否在视口内
            try:
                location = element.location
                size = element.size
                window_size = self.driver.get_window_size()
                
                # 简单的视口检查
                if (location['y'] >= 0 and location['y'] < window_size['height'] and
                    location['x'] >= 0 and location['x'] < window_size['width']):
                    car_info["in_viewport"] = True
            except:
                pass
            
            return car_info
            
        except Exception as e:
            print(f"    提取车型 {index} 信息时出错: {e}")
            return None
    
    def analyze_carousel_controls(self):
        """分析轮播控制按钮"""
        try:
            print(f"  🎮 分析轮播控制按钮:")
            
            # 查找下一页按钮
            next_selectors = [
                'button[aria-label*="next"]',
                'button[aria-label*="Next"]',
                'button[action="next"]',
                'button[class*="next"]',
                '[class*="next"] button'
            ]
            
            next_button_found = False
            for selector in next_selectors:
                try:
                    buttons = self.driver.find_elements(By.CSS_SELECTOR, selector)
                    for button in buttons:
                        if button.is_displayed() and button.is_enabled():
                            aria_label = button.get_attribute('aria-label')
                            print(f"    ✓ 找到下一页按钮: {selector}, aria-label: {aria_label}")
                            next_button_found = True
                            break
                    if next_button_found:
                        break
                except Exception:
                    continue
            
            # 查找上一页按钮
            prev_selectors = [
                'button[aria-label*="prev"]',
                'button[aria-label*="Prev"]', 
                'button[aria-label*="previous"]',
                'button[action="prev"]',
                'button[class*="prev"]'
            ]
            
            prev_button_found = False
            for selector in prev_selectors:
                try:
                    buttons = self.driver.find_elements(By.CSS_SELECTOR, selector)
                    for button in buttons:
                        if button.is_displayed() and button.is_enabled():
                            aria_label = button.get_attribute('aria-label')
                            print(f"    ✓ 找到上一页按钮: {selector}, aria-label: {aria_label}")
                            prev_button_found = True
                            break
                    if prev_button_found:
                        break
                except Exception:
                    continue
            
            if not next_button_found:
                print(f"    ⚠️  未找到下一页按钮")
            if not prev_button_found:
                print(f"    ⚠️  未找到上一页按钮")
                
        except Exception as e:
            print(f"    ❌ 分析轮播控制按钮时出错: {e}")
    
    def perform_carousel_navigation(self):
        """执行轮播导航获取所有车型"""
        try:
            all_cars = set()  # 使用set避免重复
            
            # 首先收集当前可见的车型
            current_cars = self.get_current_visible_cars()
            for car in current_cars:
                all_cars.add(car["data_cy"])
            
            print(f"    初始可见车型: {len(current_cars)} 个")
            
            # 执行下一页点击，直到回到起始状态
            max_clicks = 10  # 防止无限循环
            click_count = 0
            seen_states = []
            
            while click_count < max_clicks:
                # 点击下一页
                if self.click_next_button():
                    click_count += 1
                    self.analysis_data["carousel_navigation"]["next_button_clicks"] = click_count
                    time.sleep(2)
                    
                    # 获取点击后的车型状态
                    current_cars = self.get_current_visible_cars()
                    current_state = [car["data_cy"] for car in current_cars if car["visible"]]
                    
                    print(f"    第 {click_count} 次点击后，可见车型: {current_state}")
                    
                    # 收集新发现的车型
                    for car in current_cars:
                        if car["data_cy"]:
                            all_cars.add(car["data_cy"])
                    
                    # 检查是否回到了之前的状态（轮播完成）
                    if current_state in seen_states:
                        print(f"    ✅ 检测到轮播循环，停止点击")
                        break
                    
                    seen_states.append(current_state)
                else:
                    print(f"    ❌ 无法点击下一页按钮")
                    break
            
            print(f"  📊 轮播导航结果:")
            print(f"    - 总点击次数: {click_count}")
            print(f"    - 发现的车型总数: {len(all_cars)}")
            print(f"    - 车型列表: {list(all_cars)}")
            
            # 如果需要，使用上一页按钮回到第一个车型
            if click_count > 0:
                print(f"  🔄 使用上一页按钮回到第一个车型...")
                self.reset_to_first_car(click_count)
            
            self.analysis_data["final_car_count"] = len(all_cars)
            self.analysis_data["cars_discovered"] = list(all_cars)
            
            return list(all_cars)
            
        except Exception as e:
            print(f"  ❌ 执行轮播导航时出错: {e}")
            return []
    
    def get_current_visible_cars(self):
        """获取当前可见的车型"""
        try:
            elements = self.driver.find_elements(By.CSS_SELECTOR, 'div[data-cy][class*="ProductTile"]')
            cars = []
            
            for i, element in enumerate(elements):
                car_info = self.extract_car_basic_info(element, i+1)
                if car_info:
                    cars.append(car_info)
            
            return cars
        except Exception as e:
            print(f"    获取可见车型时出错: {e}")
            return []
    
    def click_next_button(self):
        """点击下一页按钮"""
        try:
            next_button = self.driver.find_element(By.CSS_SELECTOR, 'button[aria-label="Move to next element"][action="next"]')
            if next_button.is_displayed() and next_button.is_enabled():
                self.driver.execute_script("arguments[0].click();", next_button)
                return True
            return False
        except Exception:
            return False
    
    def click_prev_button(self):
        """点击上一页按钮"""
        try:
            prev_button = self.driver.find_element(By.CSS_SELECTOR, 'button[aria-label="Move to previous element"][action="prev"]')
            if prev_button.is_displayed() and prev_button.is_enabled():
                self.driver.execute_script("arguments[0].click();", prev_button)
                return True
            return False
        except Exception:
            return False
    
    def reset_to_first_car(self, clicks_to_undo):
        """使用上一页按钮回到第一个车型"""
        try:
            for i in range(clicks_to_undo):
                if self.click_prev_button():
                    self.analysis_data["carousel_navigation"]["prev_button_clicks"] += 1
                    time.sleep(1)
                    print(f"    第 {i+1} 次上一页点击")
                else:
                    print(f"    ❌ 第 {i+1} 次上一页点击失败")
                    break
            
            print(f"  ✅ 完成回到第一个车型的操作")
        except Exception as e:
            print(f"  ❌ 回到第一个车型时出错: {e}")
    
    def verify_final_results(self):
        """验证最终结果"""
        try:
            final_cars = self.get_current_visible_cars()
            
            print(f"  📋 最终验证结果:")
            print(f"    - 当前页面车型数: {len(final_cars)}")
            print(f"    - 发现的总车型数: {self.analysis_data['final_car_count']}")
            print(f"    - 期望车型数: 7")
            
            # 检查是否达到期望的7个车型
            if self.analysis_data['final_car_count'] == 7:
                print(f"  ✅ 车型数量正确！发现了期望的7个车型")
                self.analysis_data["analysis_notes"].append("✅ 成功发现7个车型，符合预期")
            else:
                print(f"  ⚠️  车型数量不符合预期！发现 {self.analysis_data['final_car_count']} 个，期望 7 个")
                self.analysis_data["analysis_notes"].append(f"⚠️ 车型数量异常：发现 {self.analysis_data['final_car_count']} 个，期望 7 个")
            
            return self.analysis_data['final_car_count'] == 7
            
        except Exception as e:
            print(f"  ❌ 验证最终结果时出错: {e}")
            return False
    
    def generate_analysis_report(self):
        """生成分析报告"""
        try:
            report = {
                "analysis_time": time.strftime("%Y-%m-%d %H:%M:%S"),
                "stage1_logic_verification": self.analysis_data,
                "key_findings": {
                    "cookies_processing": "成功" if self.analysis_data["cookies_handled"] else "需要优化",
                    "carousel_functionality": "正常" if self.analysis_data["carousel_navigation"]["next_button_clicks"] > 0 else "异常",
                    "car_discovery": "完整" if self.analysis_data["final_car_count"] == 7 else "不完整",
                    "data_extraction_points": {
                        "car_selector": "div[data-cy][class*='ProductTile']",
                        "next_button": "button[aria-label='Move to next element'][action='next']", 
                        "prev_button": "button[aria-label='Move to previous element'][action='prev']",
                        "price_selector": "包含 £ 符号的文本元素"
                    }
                },
                "recommendations": []
            }
            
            # 生成建议
            if not self.analysis_data["cookies_handled"]:
                report["recommendations"].append("需要改进Cookie处理逻辑")
            
            if self.analysis_data["final_car_count"] != 7:
                report["recommendations"].append("需要优化轮播导航逻辑以确保发现所有7个车型")
            
            if self.analysis_data["carousel_navigation"]["next_button_clicks"] == 0:
                report["recommendations"].append("轮播按钮点击逻辑需要修复")
            
            # 保存到文件
            with open('stage1_analysis_report.json', 'w', encoding='utf-8') as f:
                json.dump(report, f, indent=2, ensure_ascii=False)
            
            print(f"\n📄 分析报告已保存到 stage1_analysis_report.json")
            return report
            
        except Exception as e:
            print(f"生成分析报告时出错: {e}")
            return None

def main():
    """主函数"""
    analyzer = Stage1Analyzer()
    success = analyzer.analyze_stage1_logic()
    
    if success:
        print("\n🎉 第1阶段逻辑验证完成！")
    else:
        print("\n❌ 第1阶段逻辑验证失败！")

if __name__ == "__main__":
    main()
